using System;
using System.Data;
using System.Web;
using System.Collections;
using System.Web.Services;
using System.Web.Services.Protocols;
using System.ComponentModel;
using System.Security.Principal;
using System.IO;
using System.Text;

using Policy = PHSRAG.Insight21.Policy;
using System.Data.SqlClient;
using Utility = PHSRAG.Utility;
using PHSRAG.Insight21.Humans;
using CDS = PHSRAG.Insight21.CDS;
using APDocConvNET;
using PHSRAG.Security;
using System.Xml.Serialization;
using FormsManagement = PHSRAG.Insight21.FormsManagement;
using SerializedForms = PHSRAG.Insight21.FormsManagement.Serialization;
using PHSRAG.SharePointUtility;
using ibex4;
namespace InsightServiceUtility
{
    /// <summary>
    /// Summary description for OfficeAutomationDocumentUtility
    /// </summary>
    [WebService(Namespace = "http://www.partners.org/webservices/PHSRAG/InsightServiceUtility/")]
    [System.Web.Services.WebServiceBindingAttribute(Name = "RepositorySoap", Namespace = "http://www.partners.org/webservices/PHSRAG/InsightServiceUtility/")]
    public class DocumentUtility : System.Web.Services.WebService
    {
        #region Constants
        private const string isIdenticalFile = "FileIdentical";
        private const string isProtectedFile = "FileProtected";
        #endregion

        /// <summary>
        /// This method will convert the document identified by the documentid to PDF
        /// It has the oneway attribute to true so the control is returned right away to the callee;
        /// This method was created as a quick fix because the async invocation of the ConvertToPDF method was not working right
        /// This will need to be reviewed
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>N/A</returns>
        [WebMethod]
        [SoapDocumentMethod(OneWay = true)]
        public void ConvertToPDFOneWay(int documentId, int pdfTimeout, string insightConnectionString)
        {
            /*We can get rid of the timeout but removing this now will result in the change 
             * of signature and impact the application code. This should be refactored for the next release.
             */
            this.ConvertToPDF(documentId, insightConnectionString);
        }

        [WebMethod]
        [SoapDocumentMethod(OneWay = true)]
        public void ConvertToPDFOneWayFromSharePoint(string insightConnectionString, int documentId, string folderHierarchy)
        {
            /*We can get rid of the timeout but removing this now will result in the change 
             * of signature and impact the application code. This should be refactored for the next release.
             */
            this.ConvertToPDFFromSharePoint(insightConnectionString, documentId, folderHierarchy);
        }
        /// <summary>
        /// This private method will convert the document identified by the documentid to PDF and return the CDS.Document object
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>N/A</returns>
        private CDS.Document ConverToPDFInternal(int documentId, string insightConnectionString)
        {
            Policy.ICachePolicy cachePolicy = new Policy.NullCachePolicy();
            CDS.Document doc = new PHSRAG.Insight21.CDS.Document(cachePolicy);

            doc.Load(insightConnectionString, documentId);
            string tempFilename = doc.WriteTemporaryFile(doc.Extension);

            string pdfFileName = Path.ChangeExtension(tempFilename, ".PDF");
            AutomationDocumentHelper.ConvertToPDF(tempFilename, pdfFileName, doc.Extension);

            doc.PDFBlob = (File.Exists(pdfFileName)) ? DocumentHelper.GetBytesFromFile(pdfFileName) : null;

            //Delete the temp
            try
            {
                if (File.Exists(tempFilename)) File.Delete(tempFilename);
            }
            catch
            {

            }
                    //Delete PDF files
            try
            {
                if (File.Exists(pdfFileName)) File.Delete(pdfFileName);
            }
            catch
            {

            }
            return doc;
        }
        /// <summary>
        /// This private method will convert the document identified by the documentid to PDF and return the CDS.Document object
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>N/A</returns>
        private CDS.Document ConverToPDFInternalFromSharePoint(int documentId, string folderHierarchy)
        {
            Policy.ICachePolicy cachePolicy = new Policy.NullCachePolicy();
            CDS.Document doc = new PHSRAG.Insight21.CDS.Document(cachePolicy);
            doc.FolderHierarchy = folderHierarchy;

            doc.IsSharePointDocument = true;
            string fileExtention = Path.GetExtension(folderHierarchy);
            string tempFilename = doc.WriteTemporaryFile(fileExtention);
            string pdfFileName = Path.ChangeExtension(tempFilename, ".PDF");

            AutomationDocumentHelper.ConvertToPDF(tempFilename, pdfFileName, fileExtention);


            doc.FilePath = pdfFileName;
            //attachmentTitle.PDFBlob = (File.Exists(pdfFileName)) ? DocumentHelper.GetBytesFromFile(pdfFileName) : null;

            //Delete the file that got converted to PDF
            try
            {
                if (File.Exists(tempFilename)) File.Delete(tempFilename);
            }
            catch (Exception ex)
            {
                Utility.ExceptionReport.WriteToEventLog("Error deleting temp file", ex,
                   true, Utility.ExceptionReport.ReportType.Error);
            }

            return doc;
        }

        /// <summary>
        /// This method will convert the document identified by the documentid to PDF
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>OperationResult object</returns>
        [WebMethod]
        public OperationResult ConvertToPDF(int documentId, string insightConnectionString)
        {
            OperationResult oResult = new OperationResult();
            CDS.Document doc = null;
            try
            {
                doc = this.ConverToPDFInternal(documentId, insightConnectionString);
            }
            catch (Exception ex)
            {
                oResult.ResultCode = OperationResult.ResultCodes.Failure;
                oResult.ErrorMessage = ex.Message;
                Utility.EmailNotification.SendEmail("GetPDFDocument()\r Document object is null:" + (doc == null) + "\r" + ex.Message + "\r Stack Trace:\r" + ex.StackTrace);
            }
            finally
            {
                if (doc != null) doc.SavePDFFile(insightConnectionString);
            }
            return oResult;
        }

        /// <summary>
        /// This method will convert the document identified by the documentid to PDF
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>OperationResult object</returns>
        [WebMethod]
        public OperationResult ConvertToPDFFromSharePoint(string insightConnectionString, int documentId, string folderHierarchy)
        {
            OperationResult oResult = new OperationResult();
            CDS.Document doc = null;
            try
            {
                doc = this.ConverToPDFInternalFromSharePoint(documentId, folderHierarchy);
                if (doc != null)
                {
                    string sExt = Path.GetExtension(folderHierarchy);
                    doc.FolderHierarchy = doc.FolderHierarchy.Replace(sExt, ".pdf");
                    doc.SavePdfToSharePoint();
                    //Mark as converted to pdf
                    doc.UpdateConvertedToPdfFlag(insightConnectionString, documentId);

                }

            }
            catch (Exception ex)
            {
                oResult.ResultCode = OperationResult.ResultCodes.Failure;
                oResult.ErrorMessage = ex.Message;
                Utility.EmailNotification.SendEmail("GetPDFDocument()\r Document object is null:" + (doc == null) + "\r" + ex.Message + "\r Stack Trace:\r" + ex.StackTrace);
            }
            finally
            {

            }
            return oResult;
        }
        /// <summary>
        /// This method will be called synchronously;
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>Opertaional results</returns>
        [WebMethod]
        public byte[] GetPDFDocument(int documentId, int pdfTimeout, string insightConnectionString)
        {
            try
            {
                //Save to the database
                CDS.Document doc = this.ConverToPDFInternal(documentId, insightConnectionString);

                if (doc != null)
                {
                    doc.SavePDFFile(insightConnectionString);
                    return doc.PDFBlob;
                }
            }
            catch (Exception ex)
            {
                //Utility.ExceptionReport.WriteToEventLog(string.Format("Error occured while converting the document to temporary file with the documentId = {}", documentId), ex, true, Utility.ExceptionReport.ReportType.Error);
                Utility.EmailNotification.SendEmail("GetPDFDocument()\r" + ex.Message + " \r Stack Trace: \r" + ex.StackTrace);
            }
            return null;
        }

        [WebMethod]
        public OperationResult TestEmail()
        {
            OperationResult oResult = new OperationResult();
            try
            {
                throw new Exception("This is a test error from activepdf on PHSWEB127");
            }
            catch (Exception ex)
            {
                oResult.ResultCode = OperationResult.ResultCodes.Failure;
                oResult.ErrorMessage = ex.Message;
                Utility.EmailNotification.SendEmail(ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
            }
            return oResult;
        }

        /// <summary>
        /// This method will merge all documents attached to a particluar protocol specified by protocoldocumentids
        /// </summary>
        /// <param name="documentId">documentId pertaining to the document that needs to be converted</param>
        /// <param name="pdfTimeout">timeout period to convert the document pertaining to the passed in Id</param>
        /// <param name="insightConnectionString">database connectionstring to save the converted document</param>
        /// <returns>Opertaional results</returns>
        private string GetMergedPDFDocument(string protocolDocumentIds, byte[] serializedPDF, string insightConnectionString, string[] staffNamesWithTC, byte[][] trainingCertificates, string stagedOutpurFolder)
        {
            OperationResult oResult = new OperationResult();
            Policy.ICachePolicy cachePolicy = new Policy.NullCachePolicy();

            string[] al = protocolDocumentIds.Split('|');

            // include attachments
            APToolkitNET.Toolkit pdfToolKit = new APToolkitNET.Toolkit();
            // Go thru the Protocol Documents creating a temporary file for each document
            ArrayList temporaryFiles = new ArrayList();
            ArrayList pdfFileCollection = new ArrayList(al.Length);

            try
            {
                //add staff certifications
                for (int i = 0; i < staffNamesWithTC.Length; i++)
                {
                    ProtocolDocument proDoc = new ProtocolDocument(cachePolicy);
                    proDoc.Name = staffNamesWithTC[i];
                    CDS.Document doc = new PHSRAG.Insight21.CDS.Document(cachePolicy);
                    doc.Blob = trainingCertificates[i];
                    doc.Name = string.Format("{0}.pdf", staffNamesWithTC[i]);
                    proDoc.ElectronicFile = doc;
                    TemporaryPdfFile tempPdfFile = new TemporaryPdfFile();
                    tempPdfFile.Name = proDoc.Name;
                    pdfFileCollection.Add(tempPdfFile);
                    tempPdfFile.FileName = proDoc.ElectronicFile.WriteTemporaryFile(".PDF");
                    temporaryFiles.Add(tempPdfFile.FileName);

                    int pageCount = pdfToolKit.NumPages(tempPdfFile.FileName);

                    if (pageCount > 0)
                    {
                        tempPdfFile.PageCount = pageCount;
                    }
                    else
                    {
                        tempPdfFile.Write(ref pdfToolKit, string.Format("{0} cannot be included, may contain PDF security.", tempPdfFile.Name));
                        temporaryFiles.Add(tempPdfFile.FileName);
                    }
                }
                foreach (string pDId in al)
                {
                    if (string.IsNullOrEmpty(pDId))
                        continue;
                    ProtocolDocument protocolDocument = new ProtocolDocument(cachePolicy);
                    protocolDocument.Load(insightConnectionString, Convert.ToInt32(pDId));
                    if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                    {
                        protocolDocument.ElectronicFile.FolderHierarchy = CreateFolderHierarchy(protocolDocument.ProtocolId, protocolDocument.ElectronicFile.Id, protocolDocument.FileName);
                        protocolDocument.ElectronicFile.IsSharePointDocument = true;
                    }
                    TemporaryPdfFile tempPdfFile = new TemporaryPdfFile();

                    tempPdfFile.Name = protocolDocument.Name;
                    pdfFileCollection.Add(tempPdfFile);

                    if (".PDF" == protocolDocument.ElectronicFile.Extension)
                    {
                        tempPdfFile.FileName = protocolDocument.ElectronicFile.WriteTemporaryFile(".PDF");
                        temporaryFiles.Add(tempPdfFile.FileName);
                        int pageCount = pdfToolKit.NumPages(tempPdfFile.FileName);

                        if (pageCount > 0)
                        {
                            tempPdfFile.PageCount = pageCount;
                        }
                        else
                        {
                            tempPdfFile.Write(ref pdfToolKit, string.Format("{0} cannot be included, may contain PDF security.", tempPdfFile.Name));
                            temporaryFiles.Add(tempPdfFile.FileName);
                        }
                    }
                    else
                    {
                        string ext = string.Empty;
                        if (null != protocolDocument.ElectronicFile.PDFBlob)
                            ext = ".PDF";
                        else
                            ext = protocolDocument.ElectronicFile.Extension;

                        string tempFilename = protocolDocument.ElectronicFile.WriteTemporaryFile(ext);
                        temporaryFiles.Add(tempFilename);

                        try
                        {
                            try
                            {
                                if (null == protocolDocument.ElectronicFile.PDFBlob)
                                {
                                    //tempPdfFile.FileName =
                                    //   DocumentHelper.ConvertToPDF(tempFilename, Utility.Settings.GetKeyValue(DocumentHelper.PDFConversionTimeOut, DocumentHelper.PDFConversionDefaultTimeOut));
                                    tempPdfFile.FileName = Path.ChangeExtension(tempFilename, ".PDF");
                                    AutomationDocumentHelper.ConvertToPDF(tempFilename, tempPdfFile.FileName, protocolDocument.ElectronicFile.Extension);
                                    protocolDocument.ElectronicFile.PDFBlob = DocumentHelper.GetBytesFromFile(tempPdfFile.FileName);
                                    //DM changes
                                    protocolDocument.ElectronicFile.FilePath = tempPdfFile.FileName;
                                    string sExt = Path.GetExtension(protocolDocument.ElectronicFile.FolderHierarchy);
                                    protocolDocument.ElectronicFile.FolderHierarchy = protocolDocument.ElectronicFile.FolderHierarchy.Replace(sExt, ".pdf");
                                    protocolDocument.ElectronicFile.SavePDFFile(insightConnectionString);
                                    temporaryFiles.Add(tempPdfFile.FileName);
                                }
                                else
                                    tempPdfFile.FileName = tempFilename;
                            }
                            catch (Exception ex)
                            {
                                Utility.EmailNotification.SendEmail(ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
                            }


                            int pageCount = pdfToolKit.NumPages(tempPdfFile.FileName);

                            if (pageCount > 0)
                            {
                                tempPdfFile.PageCount = pageCount;
                            }
                            else
                            {
                                tempPdfFile.Write(ref pdfToolKit, string.Format("{0} cannot be included, may contain PDF security.", tempPdfFile.Name));
                                temporaryFiles.Add(tempPdfFile.FileName);
                            }
                        }
                        catch (Exception ex)
                        {
                            //Utility.ExceptionReport.WriteToEventLog("PDF Creation", ex, true, Utility.ExceptionReport.ReportType.Error);

                            tempPdfFile.Write(ref pdfToolKit,
                                              string.Format("Unable to generate PDF for {0}.", tempPdfFile.Name));
                            temporaryFiles.Add(tempPdfFile.FileName);
                            Utility.EmailNotification.SendEmail(ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
                        }
                    }
                }

                string outputFile = Path.GetTempFileName();
                APToolkitNET.Toolkit pdfTK = null;
                try
                {
                    /*Create final output
                    instantiate the Tool kit again due to a bug in
                    ActivePDF that doesn't like the earlier NumPages calls
                    * */
                    pdfTK = new APToolkitNET.Toolkit();
                    pdfTK.OpenOutputFile(outputFile);
                    temporaryFiles.Add(outputFile);

                    pdfTK.InputByteArray = serializedPDF;
                    int pageCount = pdfTK.NumPages("MEMORY");
                    pdfTK.CopyForm(0, 0);
                    pdfTK.CloseInputFile();

                    pdfTK.AddInternalLinkBookmark("Application", 1, 0, 0);
                    pdfTK.AddInternalLinkBookmark("Attachments", pageCount++, 0, 0);

                    foreach (TemporaryPdfFile tempPdfFile in pdfFileCollection)
                    {
                        pdfTK.MergeFile(tempPdfFile.FileName, 0, 0);
                        pdfTK.AddInternalLinkBookmark(tempPdfFile.Name, pageCount, 0, 0);
                        pageCount += tempPdfFile.PageCount;
                    }
                }
                catch (Exception ex)
                {
                    Utility.EmailNotification.SendEmail(ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
                }
                finally
                {
                    pdfTK.CloseInputFile();
                    pdfTK.CloseOutputFile();
                    pdfTK = null;
                }
                //Move the content of the temporary file to the file in Staged view app folder available on the webserver
                return WriteFileToStagingFolder(stagedOutpurFolder, outputFile);

            }
            finally
            {
                pdfFileCollection = null;

                foreach (string filename in temporaryFiles)
                {
                    try
                    {
                        if (File.Exists(filename)) File.Delete(filename);
                    }
                    catch
                    {
                        // swallow this!
                        //Utility.ExceptionReport.WriteToEventLog("View Full Application", ex, false, Utility.ExceptionReport.ReportType.Warning);
                        // Utility.EmailNotification.SendEmail(ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
                    }
                }
            }
        }

        /// <summary>
        /// Returns an altered document object by embedding the consent footer.At present will be called from the protocol object
        /// </summary>
        /// <param name="pDId">protocol document id that will have the footer embedded</param>
        /// <param name="cachePolicy">cache policy</param>
        /// <returns>document object</returns>
        [WebMethod]
        public byte[] GetConsentFormWithFooter(int pDId)
        {
            ProtocolDocument protocolDocument = new ProtocolDocument(new Policy.NullCachePolicy());
            protocolDocument.Load(Utility.DataAccess.GetConnectionString(), Convert.ToInt32(pDId));

            ConsentFormFooter consentFooter = new ConsentFormFooter();
            consentFooter.Load(Utility.DataAccess.GetConnectionString(), protocolDocument);
            string PDFFileName = string.Empty;
            try
            {
                float setting = Utility.Settings.GetKeyValue("ConsentFormFooterStartValue", 1);
                float y = setting;

                float firstRow = y + 35;
                float secondRow = y + 25;
                float thirdRow = y + 15;
                float fourthtRow = y + 5;

                float frameTop = y;
                //float frameBottom = y + 55;
                float frameBottom = y + 44;
                const float frameLeft = 5;
                const float frameRight = 607;

                Policy.ICachePolicy cachePolicy = new Policy.NullCachePolicy();
                CDS.Document consentDocument = new CDS.Document(cachePolicy);
                consentDocument.Load(Utility.DataAccess.GetConnectionString(), consentFooter.DocumentId);
                string inputFile = "MEMORY";

                if (!consentDocument.IsConvertedToPdf && ".PDF" != consentDocument.Extension)
                {
                    //DM changes for document1
                    if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                    {

                        consentDocument.FolderHierarchy = CreateFolderHierarchy(protocolDocument.ProtocolId,
                        consentDocument.Id, protocolDocument.FileName);

                        consentDocument.IsSharePointDocument = true;
                    }
                    string tempFilename = consentDocument.WriteTemporaryFile(consentDocument.Extension);
                    inputFile = Path.ChangeExtension(tempFilename, ".PDF");
                    AutomationDocumentHelper.ConvertToPDF(tempFilename, inputFile, consentDocument.Extension);

                    //Save to the database
                    if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                    {
                        PDFFileName = Path.ChangeExtension(consentDocument.FolderHierarchy, ".PDF");
                        consentDocument.FolderHierarchy = PDFFileName;
                    }
                    consentDocument.PDFBlob = DocumentHelper.GetBytesFromFile(inputFile);
                    consentDocument.SavePDFFile(Utility.DataAccess.GetConnectionString());
                    //Save Ends
                    try
                    {
                        File.Delete(tempFilename);
                    }
                    catch (Exception ex)
                    {
                        Utility.EmailNotification.SendEmail(ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
                    }
                }


                APToolkitNET.Toolkit apToolKit = new APToolkitNET.Toolkit();
                if (null == apToolKit)
                {
                    throw new Exception("Unable to instantiate active PDF Toolkit");
                }

                // footer PDF
                string footer = Path.GetTempFileName();
                apToolKit.OpenOutputFile(footer);

                apToolKit.SetFont("Helvetica|bold=1", 8, 0);

                apToolKit.PrintText(10, firstRow, string.Format("Subject Population: {0}", consentFooter.ConsentFormName));

                apToolKit.PrintText(10, secondRow, string.Format("IRB Protocol No: {0}", consentFooter.IrbProtocolNumber));
                apToolKit.PrintText(210, secondRow, string.Format("Sponsor Protocol No: {0}", consentFooter.SponsorProtocolNumber));

                apToolKit.PrintText(10, thirdRow, string.Format("Consent Form Valid Date: {0}", consentFooter.ConsentFormApprovalDate));
                apToolKit.PrintText(210, thirdRow, string.Format("IRB Amendment No: {0}", consentFooter.IrbAmendmentNumber));
                apToolKit.PrintText(400, thirdRow, string.Format("Sponsor Amendment No: {0}", consentFooter.SponsorApprovalNumber));

                apToolKit.PrintText(10, fourthtRow, string.Format("IRB Expiration Date: {0}", consentFooter.IrbExpirationDate));
                apToolKit.PrintText(210, fourthtRow, string.Format("IRB Amendment Approval Date: {0}", consentFooter.IrbAmendmentApprovalDate));

                apToolKit.MoveTo(frameLeft, frameTop);
                apToolKit.DrawTo(frameRight, frameTop);

                apToolKit.MoveTo(frameRight, frameTop);
                apToolKit.DrawTo(frameRight, frameBottom);

                apToolKit.MoveTo(frameRight, frameBottom);
                apToolKit.DrawTo(frameLeft, frameBottom);

                apToolKit.MoveTo(frameLeft, frameBottom);
                apToolKit.DrawTo(frameLeft, frameTop);

                apToolKit.CloseOutputFile();

                // consent form pdf
                apToolKit.OpenOutputFile("MEMORY");

                if ("MEMORY" == inputFile)
                {
                    if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                    {
                        consentDocument.IsSharePointDocument = true;
                        consentDocument.FolderHierarchy = CreateFolderHierarchy(protocolDocument.ProtocolId, consentDocument.Id, protocolDocument.FileName);
                    }
                    if (".PDF" == consentDocument.Extension)
                    {
                        apToolKit.InputByteArray = consentDocument.Blob;
                    }
                    else if (consentDocument.IsConvertedToPdf)
                    {
                        PDFFileName = Path.ChangeExtension(consentDocument.FolderHierarchy, ".PDF");
                        consentDocument.FolderHierarchy = PDFFileName;
                        apToolKit.InputByteArray = consentDocument.PDFBlob;
                    }
                }
                apToolKit.OpenInputFile(inputFile);

                apToolKit.AddLogo(footer, 0);

                apToolKit.CopyForm(0, 0);
                apToolKit.CloseInputFile();
                apToolKit.CloseOutputFile();

                return apToolKit.BinaryImage();
            }
            catch (Exception ex)
            {
                Utility.EmailNotification.SendEmail("GetConsentFormWithFooter()\r" + ex.Message + "\r Stack Trace: \r" + ex.StackTrace + PDFFileName);
                throw ex;
            }

        }
        /// <summary>
        /// Saves the pdf file to the database
        /// </summary>
        /// <param name="insightConnectionString">InsightConnectionString</param>
        /// <param name="newFileName">New file name</param>
        ///  /// <param name="fileNameInDb"> File name in the database</param>
        /// <returns>Returns the document Id created for the new document in the database</returns>
        [WebMethod]
        public int SaveFileToDatabase(string insightConnectionString, string newFileName, string fileNameInDb)
        {
            FileStream fs = null;
            try
            {
                CDS.Document doc = new CDS.Document(new Policy.NullCachePolicy());
                doc.Name = fileNameInDb;
                WindowsImpersonationContext wic = Authenticator.ImpersonateUser(
                    Utility.Settings.GetKeyValue("ServiceAccount", "rag29"),
                    Utility.Settings.GetKeyValue("ServiceAccountPwd", "zohcq"),
                    Authenticator.LogonType.NewCredentials, Authenticator.LogonProvider.WinNT50);
                string newFilePath = Path.Combine(Utility.Settings.GetKeyValue("InsightAttachmentsPath", string.Empty), newFileName);
                fs = new FileStream(newFilePath,
                        FileMode.Open, FileAccess.Read);
                byte[] data = new byte[fs.Length];
                fs.Read(data, 0, System.Convert.ToInt32(fs.Length));
                fs.Close();

                doc.Blob = data;
                doc.Save(insightConnectionString);

                //File.Delete(newFilePath);

                Authenticator.RevertUser(wic);
                return doc.Id;
            }
            catch (Exception ex)
            {
                if (fs != null)
                    fs.Close();
                //Utility.ExceptionReport.WriteToEventLog(String.Format("Failed to save the file {0} to Database.", newFileName),
                //    ex, true, Utility.ExceptionReport.ReportType.Error);
                Utility.EmailNotification.SendEmail("SaveFileToDatabase() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
                return -1;
            }
        }

        [WebMethod]
        public int SaveFileToSharepoint(string insightConnectionString, string newFileName, string fileNameInDb, string[] metadata, string folderHierarchy)
        {
            FileStream fs = null;
            try
            {
                CDS.Document doc = new CDS.Document(new Policy.NullCachePolicy());
                doc.Name = fileNameInDb;

                string newFilePath = Path.Combine(Utility.Settings.GetKeyValue("InsightAttachmentsPath", string.Empty), newFileName);

                doc.FilePath = newFilePath;
                doc.FolderHierarchy = folderHierarchy;
                doc.Metadata = GetMetaDataHashTable(metadata);
                doc.IsSharePointDocument = true;
                doc.Save(insightConnectionString);
                return doc.Id;
            }
            catch (Exception ex)
            {
                if (fs != null)
                    fs.Close();
                Utility.ExceptionReport.WriteToEventLog(String.Format("Failed to save the file {0} to Database.", newFileName),
                    ex, true, Utility.ExceptionReport.ReportType.Error);
                Utility.EmailNotification.SendEmail("SaveFileToSharepoint() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
                return -1;
            }
        }
        /// <summary>
        /// Generate the pdf of the occupational healthcare form
        /// </summary>
        /// <param name="protocolId">protocol Id</param>
        /// <param name="personId">Person Id to generate the occupation healthcare pdf</param>
        /// <param name="viewAppStagingFolder">Application staging folder on the webserver that holds the generated files for transmission to the client</param>
        /// <param name="certificateType">The type of staff certificate to return</param>
        /// <returns>string path to file</returns>
        //[WebMethod]
        //public string  GetStaffCertificate(int protocolId, int personId, string viewAppStagingFolder, string certificateType)
        //{
        //    string stagedOutputFile = string.Empty;
        //    try
        //    {
        //        string downloadFilename;
        //        switch (certificateType)
        //        {
        //            case FormsManagement.Constants.AnimalsQuestionnaireCommonFormNames.OccHealth:
        //                downloadFilename = "OccHealthSurvey.pdf";
        //                break;
        //            case FormsManagement.Constants.AnimalsQuestionnaireCommonFormNames.Experience:
        //                downloadFilename = "QualificationsAndExperience.pdf";
        //                break;
        //            default:
        //                throw new ApplicationException("Certificate type is not yet supported.");
        //        }

        //        //convert to pdf and get the temp location in filePath
        //        string appPath = Server.MapPath("");
        //        string xslFilePath = Path.Combine(Server.MapPath("."), Utility.Settings.GetKeyValue("QuestionnaireAnswerToPdfXSFOFileName", ""));
        //        if (personId == 0)
        //            throw new Exception("Mail cannot be sent.PersonId is unknown");
        //        CDS.Person user = new PHSRAG.Insight21.CDS.Person(new Policy.NullCachePolicy());
        //        user.Load(Utility.DataAccess.GetConnectionString(), personId);
        //        FormsManagement.Serialization.Forms forms = user.SerializableCertificates(new Policy.NullCachePolicy(),
        //                                                                                Utility.DataAccess.ConnectionString,
        //                                                                                certificateType);
        //        if (forms == null)
        //            throw new Exception(string.Format("{0} form not found. Mail cannot be sent.", certificateType));

        //        if (protocolId == 0)
        //            throw new Exception("E-Mail cannot be sent. Module type is not known.");
        //        Protocol protocol = new Protocol(new Policy.NullCachePolicy());
        //        protocol.Load(Utility.DataAccess.GetConnectionString(), protocolId);

        //        forms.ModuleType = protocol.ModuleType;

        //        string logoPath = Path.Combine(Server.MapPath("."), Utility.Settings.GetKeyValue("PartnersLogo", ""));

        //        forms.LogoLocation = logoPath;

        //        //add the current user to the staff section
        //        forms.StudyStaff = new ArrayList();
        //        FormsManagement.Serialization.FormStudyPerson formStudyPerson = new PHSRAG.Insight21.FormsManagement.Serialization.FormStudyPerson();
        //        formStudyPerson.Name = string.Format("{0}, {1}", user.LastName, user.FirstName);
        //        formStudyPerson.Degrees = user.DegreeList;
        //        forms.StudyStaff.Add(formStudyPerson);

        //        IRBDocment irbDocument = new IRBDocment(new Policy.NullCachePolicy());
        //        CDS.Document attachmentTitle = irbDocument.CreateDocument(Server.MapPath("."), downloadFilename, xslFilePath, forms, null);
        //        string outputFile = attachmentTitle.WriteTemporaryFile(".PDF");

        //        try
        //        {
        //            stagedOutputFile = WriteFileToStagingFolder(viewAppStagingFolder, outputFile);
        //        }
        //        catch (Exception ex)
        //        {
        //            //Utility.ExceptionReport.WriteToEventLog(String.Format("Failed while impersonating and saving the file {0} to staging folder.", outputFile),
        //            //ex, true, Utility.ExceptionReport.ReportType.Error);
        //            Utility.EmailNotification.SendEmail("GetStaffCertificate() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
        //        }
        //    }
        //    catch (Exception ex)
        //    {
        //        //Utility.ExceptionReport.WriteToEventLog("GetOccHealthDocument failed", ex, true, PHSRAG.Utility.ExceptionReport.ReportType.Error);
        //        Utility.EmailNotification.SendEmail("GetStaffCertificate()\r" + ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
        //        throw ex;
        //    }
        //    return stagedOutputFile;
        //}

        /// <summary>
        /// Generate the pdf of the occupational healthcare form for a single specie.
        /// </summary>
        /// <param name="protocolId">protocol Id</param>
        /// <param name="personId">Person Id to generate the occupation healthcare pdf</param>
        /// <param name="Questionnaire Id">Questionnaire Id to get just one.</param>
        /// <param name="viewAppStagingFolder">Application staging folder on the webserver that holds the generated files for transmission to the client</param>
        /// <param name="certificateType">The type of staff certificate to return</param>
        /// <returns>string path to file</returns>
        [WebMethod]
        public string GetStaffCertificateForSpecie(int protocolId, int personId, string viewAppStagingFolder, string certificateType)
        {
            string stagedOutputFile = string.Empty;
            try
            {
                string downloadFilename;
                switch (certificateType)
                {
                    case FormsManagement.Constants.AnimalsQuestionnaireCommonFormNames.OccHealth:
                        downloadFilename = "OccHealthSurvey.pdf";
                        break;
                    case FormsManagement.Constants.AnimalsQuestionnaireCommonFormNames.Experience:
                        downloadFilename = "QualificationsAndExperience.pdf";
                        break;
                    default:
                        throw new ApplicationException("Certificate type is not yet supported.");
                }

                //convert to pdf and get the temp location in filePath
                string appPath = Server.MapPath("");
                string xslFilePath = Path.Combine(Server.MapPath("."), Utility.Settings.GetKeyValue("QuestionnaireAnswerToPdfXSFOFileName", ""));
                if (personId == 0)
                    throw new Exception("Mail cannot be sent.PersonId is unknown");
                CDS.Person user = new PHSRAG.Insight21.CDS.Person(new Policy.NullCachePolicy());
                user.Load(Utility.DataAccess.GetConnectionString(), personId);
                FormsManagement.Serialization.Forms forms = user.SerializableCertificates(new Policy.NullCachePolicy(),
                                                                                        Utility.DataAccess.ConnectionString,
                                                                                        certificateType);
                if (forms == null)
                    throw new Exception(string.Format("{0} form not found. Mail cannot be sent.", certificateType));

                if (protocolId == 0)
                    throw new Exception("E-Mail cannot be sent. Module type is not known.");
                Protocol protocol = new Protocol(new Policy.NullCachePolicy());
                protocol.Load(Utility.DataAccess.GetConnectionString(), protocolId);

                forms.ModuleType = protocol.ModuleType;

                string logoPath = Path.Combine(Server.MapPath("."), Utility.Settings.GetKeyValue("PartnersLogo", ""));

                forms.LogoLocation = logoPath;

                //add the current user to the staff section
                forms.StudyStaff = new ArrayList();
                FormsManagement.Serialization.FormStudyPerson formStudyPerson = new PHSRAG.Insight21.FormsManagement.Serialization.FormStudyPerson();
                formStudyPerson.Name = string.Format("{0}, {1}", user.LastName, user.FirstName);
                formStudyPerson.Degrees = user.DegreeList;
                forms.StudyStaff.Add(formStudyPerson);

                IRBDocment irbDocument = new IRBDocment(new Policy.NullCachePolicy());
                CDS.Document doc = irbDocument.CreateDocument(Server.MapPath("."), downloadFilename, xslFilePath, forms, null);
                string outputFile = doc.WriteTemporaryFile(".PDF");

                try
                {
                    stagedOutputFile = WriteFileToStagingFolder(viewAppStagingFolder, outputFile);
                }
                catch (Exception ex)
                {
                    //Utility.ExceptionReport.WriteToEventLog(String.Format("Failed while impersonating and saving the file {0} to staging folder.", outputFile),
                    //ex, true, Utility.ExceptionReport.ReportType.Error);
                    Utility.EmailNotification.SendEmail("GetStaffCertificate() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
                }
            }
            catch (Exception ex)
            {
                //Utility.ExceptionReport.WriteToEventLog("GetOccHealthDocument failed", ex, true, PHSRAG.Utility.ExceptionReport.ReportType.Error);
                Utility.EmailNotification.SendEmail("GetStaffCertificate()\r" + ex.Message + "\r Stack Trace: \r" + ex.StackTrace);
                throw ex;
            }
            return stagedOutputFile;
        }

        /// <summary>
        /// Generate the application document(View app/View full app) for the process/protocol
        /// </summary>
        /// <param name="protocolProcessId">process Id to which the document has to be generated</param>
        /// <param name="viewAppStagingFolder">Staging folder on the web server to save the document(PDF) generated</param>
        /// <param name="viewApplicationDocType">type of generation(Simple/full)</param>
        /// <returns></returns>
        [WebMethod]
        public string GetApplicationDocument(int protocolProcessId, string viewAppStagingFolder, string viewApplicationDocType)
        {
            ProtocolProcess protocolProcess = ProtocolProcess.GetProtocolProcess(Utility.DataAccess.GetConnectionString(), protocolProcessId, new Policy.NullCachePolicy(), null);
            string viewApplicationType = (viewApplicationDocType == string.Empty) ? Constants.ViewApplicationType.Simple : viewApplicationDocType;

            IRBDocment irbDoc = new IRBDocment(new Policy.NullCachePolicy());
            byte[] pdfOutput = irbDoc.CreateInitialDocument(Server.MapPath("."), viewApplicationType, protocolProcessId);
            ArrayList al = irbDoc.GetProtocolDocuments(viewApplicationType, Server.MapPath(""), false, protocolProcess);
            string outputFile = string.Empty;
            string viewFullAppPath = string.Empty;
            if (viewApplicationType == Constants.ViewApplicationType.Simple || (al == null || al.Count == 0))
            {
                CDS.Document doc = new PHSRAG.Insight21.CDS.Document(new Policy.NullCachePolicy());
                doc.Name = "Application.pdf";
                doc.Blob = pdfOutput;
                outputFile = doc.WriteTemporaryFile(".PDF");
                viewFullAppPath = WriteFileToStagingFolder(viewAppStagingFolder, outputFile);
            }


            else
            {
                ArrayList staffNames = new ArrayList();
                ArrayList trainingCertificates = new ArrayList();

                StringBuilder pdIds = new StringBuilder();
                foreach (ProtocolDocument pd in al)
                {
                    if (pd.Id == 0)
                    {
                        staffNames.Add(pd.Name);
                        trainingCertificates.Add(pd.ElectronicFile.Blob);
                    }
                    else
                    {
                        pdIds.Append(pd.Id + "|");
                    }
                }

                viewFullAppPath = GetMergedPDFDocument(pdIds.ToString().TrimEnd('|'), pdfOutput, Utility.DataAccess.ConnectionString, (string[])staffNames.ToArray(typeof(string)), (byte[][])trainingCertificates.ToArray(typeof(byte[])), viewAppStagingFolder);

            }

            return viewFullAppPath;

        }

        /// <summary>
        ///This method will be called ASYNCHRONOUSLY after the process is "Locked" from the PROOTOCOLDETAILS page 
        /// The method generates all Application PDF(View Full App, View App, Current View, IR) documents and stores in sharepoint
        /// </summary>
        /// <param name="protocolProcessId"></param>
        /// <param name="viewAppStagingFolder"></param>
        /// <param name="protocolId"></param>
        [WebMethod]
        [SoapDocumentMethod(OneWay = true)]
        public void GenerateAndSaveApplicationDocuments(int protocolProcessId,
            string viewAppStagingFolder,
            int protocolId)
        {

            ProtocolProcess protocolProcess = null;
            try
            {
                DocumentLibrary docLib = new DocumentLibrary();
                IRBDocment irbDocument = new IRBDocment(new Policy.NullCachePolicy());
                DeleteAppDocuments(protocolProcessId, protocolId);
                //Generate and save App
                string viewFullAppPath = this.GetApplicationDocument(protocolProcessId,
                         viewAppStagingFolder,
                         Constants.ViewApplicationType.View);
                string folderHierarchy = irbDocument.CreateFolderHierarchy(protocolProcessId, protocolId, Constants.ViewApplicationType.View);
                docLib.SaveFileToSharePoint(folderHierarchy, viewFullAppPath);

                //Generate and Save Full App
                viewFullAppPath = this.GetApplicationDocument(protocolProcessId,
                        viewAppStagingFolder,
                        Constants.ViewApplicationType.Full);
                folderHierarchy = folderHierarchy.Replace(Constants.ViewApplicationType.View, Constants.ViewApplicationType.Full);
                docLib.SaveFileToSharePoint(folderHierarchy, viewFullAppPath);
                //Generate and Save Simple
                viewFullAppPath = this.GetApplicationDocument(protocolProcessId,
                        viewAppStagingFolder,
                        Constants.ViewApplicationType.Simple);
                folderHierarchy = folderHierarchy.Replace(Constants.ViewApplicationType.View, Constants.ViewApplicationType.Simple);
                docLib.SaveFileToSharePoint(folderHierarchy, viewFullAppPath);
                //Generate and save document for IR & Curent view for this protocol 
                ProtocolVersion protocolVersion =
                           Protocol.GetLatestApplicationVersion(protocolId, Utility.DataAccess.ConnectionString, false, null);

                if (null != protocolVersion)
                {
                    protocolProcess =
                      ProtocolProcess.GetProtocolProcess(Utility.DataAccess.ConnectionString, protocolVersion.ProtocolProcessId, null, null);
                    //Generate and Save Simple
                    viewFullAppPath = this.GetApplicationDocument(protocolProcessId,
                            viewAppStagingFolder,
                            Constants.ViewApplicationType.FullUsingProtocolInformation);
                    folderHierarchy = folderHierarchy.Replace(Constants.ViewApplicationType.View, Constants.ViewApplicationType.FullUsingProtocolInformation);
                    docLib.SaveFileToSharePoint(folderHierarchy, viewFullAppPath);
                }
            }
            catch (Exception ex)
            {
                string text = string.Format("GenerateAndSaveApplicationDocuments:ProtocolProcessId={0};protocolid={1}", protocolProcessId.ToString(), protocolId.ToString());
                Utility.EmailNotification.SendEmail("WriteFileToStagingFolder() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
            }
            finally
            {
            }
        }


        /// <summary>
        ///This method will be called by the "view full application" of locked protocol processes. 
        /// If the PDF exists on SharePoint, fetch and display it. 
        /// If not generate the PDF on the fly and save it to SharePoint
        /// 
        /// </summary>
        /// <param name="protocolProcessId">Process Id of the protocol for which VFA is requested</param>
        /// <param name="viewAppStagingFolder">Share for storing the PDF</param>
        /// <param name="viewApplicationDocType">Full</param>
        /// <returns></returns>

        [WebMethod]
        public string GetAppDocumentForLockedProcess(
            int protocolProcessId,
            string viewAppStagingFolder,
            string viewApplicationDocType,
            bool hasBeenLocked,
            int protocolId)
        {

            string viewFullAppPath = string.Empty;
            string outputFile = string.Empty;
            IRBDocment irbDoc = null;
            try
            {
                /* Get PDF Blob for protocol id */
                irbDoc = new IRBDocment(new Policy.NullCachePolicy());
                byte[] vfaPDF = null;
                if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                {
                    vfaPDF = irbDoc.GetVFADocumentFromSharePoint(protocolProcessId, protocolId, viewApplicationDocType);

                }
                /* if Blob is not null, generate already saved pdf , else regenerate new pdf and save it in db */
                if (vfaPDF != null)
                {
                    //Prepare PDF, Save it in staging folder and return the path of this pdf to calling method
                    CDS.Document doc = new PHSRAG.Insight21.CDS.Document(new Policy.NullCachePolicy());
                    doc.Name = "Application.pdf";
                    doc.Blob = vfaPDF;
                    outputFile = doc.WriteTemporaryFile(".PDF");
                    viewFullAppPath = WriteFileToStagingFolder(viewAppStagingFolder, outputFile);
                }
                else
                {
                    viewFullAppPath = this.GetApplicationDocument(protocolProcessId,
                         viewAppStagingFolder,
                         viewApplicationDocType);
                    /*Save PDF asynchronously*/
                    this.SaveVFAPDFOutput(protocolProcessId, viewFullAppPath, protocolId, viewApplicationDocType);
                }
            }
            catch (Exception ex)
            {
                //Utility.ExceptionReport.WriteToEventLog("GetOccHealthDocument failed", ex, true, PHSRAG.Utility.ExceptionReport.ReportType.Error);
                throw ex;
            }
            finally
            {

            }
            return viewFullAppPath;

        }


        /// <summary>
        /// Saves the contents of the generated VFA PDF file to SharePoint 
        /// This will be called only for LOCKED protocols when the content needs to be "frozen".        
        /// </summary>
        /// <param name="filepath">File Path of the </param>        
        /// <returns></returns>
        /// 
        [SoapDocumentMethod(OneWay = true)]
        private void SaveVFAPDFOutput(int protocolProcessId, string filepath, int protocolId, string type)
        {
            try
            {
                DocumentLibrary docLib = new DocumentLibrary();
                IRBDocment irbDocument = new IRBDocment(new Policy.NullCachePolicy());
                string folderHierarchy = irbDocument.CreateFolderHierarchy(protocolProcessId, protocolId, type);
                docLib.SaveFileToSharePoint(folderHierarchy, filepath);

            }
            catch (Exception ex)
            {
                string text = string.Format("SaveVFAPDFOutput:ProtocolProcessId={0};protocolid={1}", protocolProcessId.ToString(), protocolId.ToString());
                Utility.EmailNotification.SendEmail("WriteFileToStagingFolder() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
            }
            finally
            {
            }
        }


        /// <summary>
        /// Move the contents of the generated output file to the staging folder 
        /// </summary>
        /// <param name="StagingFolderPath">Staging folder for the documents</param>
        /// <param name="outputFile">Generated output file path</param>
        /// <returns></returns>
        private string WriteFileToStagingFolder(string StagingFolderPath, string outputFile)
        {
            //string stagedOutputFile = Path.Combine(StagingFolderPath, Path.ChangeExtension(Path.GetFileName(outputFile), ".PDF"));
            /*using the GUIID to prevent the IOException (The file exists.)*/
            string stagedOutputFile = Path.Combine(StagingFolderPath, Path.ChangeExtension(System.Guid.NewGuid().ToString(), ".PDF"));

            try
            {
                WindowsImpersonationContext wic = Authenticator.ImpersonateUser(
                               Utility.Settings.GetKeyValue("ServiceAccount", "RAG29"),
                               Utility.Settings.GetKeyValue("ServiceAcountPwd", "z0hcq"),
                               Authenticator.LogonType.NewCredentials, Authenticator.LogonProvider.WinNT50);


                File.Move(outputFile, stagedOutputFile);

                Authenticator.RevertUser(wic);

                return stagedOutputFile;
            }
            catch (Exception ex)
            {
                Utility.EmailNotification.SendEmail("WriteFileToStagingFolder() - \r" + ex.Message + " - \r Inner Exception: " + ex.StackTrace);
                return string.Empty;
            }
        }

        /// <summary>
        /// Compares 2 word documents and returns the path of the differences file.
        /// </summary>
        /// <param name="pdId1"></param>
        /// <param name="pdId2"></param>

        /// <returns></returns>
        [WebMethod]
        public string CompareDocuments(string stagingFolder, string insightConnectionString, int pdId1, int pdId2)
        {
            string filePath1 = null, filePath2 = null, stagedOutputFile = null;
            try
            {
                ProtocolDocument pd1 = new ProtocolDocument(new Policy.NullCachePolicy());
                pd1.Load(insightConnectionString, pdId1);
                //DM changes for document1
                if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                {

                    pd1.ElectronicFile.FolderHierarchy = CreateFolderHierarchy(pd1.ProtocolId, pd1.ElectronicFile.Id, pd1.FileName);
                    pd1.ElectronicFile.IsSharePointDocument = true;
                }
                filePath1 = pd1.ElectronicFile.WriteTemporaryFile(pd1.ElectronicFile.Extension);

                ProtocolDocument pd2 = new ProtocolDocument(new Policy.NullCachePolicy());
                pd2.Load(insightConnectionString, pdId2);
                //DM changes for document2
                if (Utility.Settings.GetKeyValue("SaveToSharePoint", false))
                {
                    pd2.ElectronicFile.FolderHierarchy = CreateFolderHierarchy(pd2.ProtocolId, pd2.ElectronicFile.Id, pd2.FileName);
                    pd2.ElectronicFile.IsSharePointDocument = true;
                }
                filePath2 = pd2.ElectronicFile.WriteTemporaryFile(pd2.ElectronicFile.Extension);

                int CompareStatus = AutomationDocumentHelper.CompareDocuments(filePath1, filePath2);
                stagedOutputFile = Path.Combine(stagingFolder, Path.GetFileName(filePath1));

                if (CompareStatus == (int)FileCompStatus.isIdentical)     // no need to check error here, it was throw from calling AutomationDocumentHelper.CompareDocuments
                {
                    return isIdenticalFile;
                }
                else if (CompareStatus == (int)FileCompStatus.isProtected)
                {
                    return isProtectedFile;
                }

                WindowsImpersonationContext wic = Authenticator.ImpersonateUser(
                    Utility.Settings.GetKeyValue("ServiceAccount", "rag29"),
                    Utility.Settings.GetKeyValue("ServiceAccountPwd", "z0hcq"),
                    Authenticator.LogonType.NewCredentials, Authenticator.LogonProvider.WinNT50);

                File.Move(filePath1, stagedOutputFile);

                Authenticator.RevertUser(wic);

                return Path.GetFileName(stagedOutputFile);
            }
            catch (Exception ex)
            {
                //Utility.ExceptionReport.WriteToEventLog("Failed to compare word documents.", ex, true, Utility.ExceptionReport.ReportType.Error);
                Utility.EmailNotification.SendEmail(string.Format("CompareDocuments() - \r{0} - \r Inner Exception:{1}\rDiff file :{2}\rStaged File :{3}", ex.Message, ex.StackTrace, filePath1, stagedOutputFile));
                return null;
            }
            finally
            {
                if (!string.IsNullOrEmpty(filePath1) && File.Exists(filePath1))
                    File.Delete(filePath1);
                if (!string.IsNullOrEmpty(filePath2) && File.Exists(filePath2))
                    File.Delete(filePath2);
            }
        }


        /// <summary>
        /// Returns the detailed report that includes the summary and the individual reports for the specified COI Ids
        /// </summary>
        /// <returns>A Document object</returns>
        [WebMethod]
        public string GetDetailedReport(DataSet admPersonIdsForXML, string supervisorName, string stagedOutputFolder, bool filterByLatestReportingPeriod)
        {
            try
            {
                string connectionString = Utility.DataAccess.ConnectionString;
                CDS.Document summaryReport = GetSummaryReport(Server.MapPath("."), admPersonIdsForXML,
                    supervisorName, filterByLatestReportingPeriod);

                //DataTable individualReportDetails = Utility.DataAccess.GetDataTable(connectionString, "GetCOIDocuments",
                //    Utility.DataAccess.BuildSqlParameterArray("@xmlListOfAdmPersonIds", SqlDbType.Text, admPersonIdsForXML.GetXml()));


                // include attachments
                APToolkitNET.Toolkit pdfToolKit = new APToolkitNET.Toolkit();

                if (null == pdfToolKit)
                {
                    throw new Exception("Unable to create Active PDF Toolkit");
                }


                pdfToolKit.OpenOutputFile("MEMORY");
                try
                {
                    pdfToolKit.InputByteArray = summaryReport.Blob;
                    int pageCount = pdfToolKit.NumPages("MEMORY");
                    int nextBookMark = pageCount + 1;

                    try
                    {
                        pdfToolKit.CopyForm(0, 0);
                        pdfToolKit.AddInternalLinkBookmark("Summary Report", 1, 0, 0);
                        pdfToolKit.AddInternalLinkBookmark("Individual Reports", pageCount, 0, 0);
                    }
                    finally
                    {
                        pdfToolKit.CloseInputFile();
                    }


                    using (SqlDataReader rdrRptDetails = Utility.DataAccess.ExecuteReader(connectionString, "dbo.GetCOIDocuments",
                        Utility.DataAccess.BuildSqlParameterArray("@xmlListOfAdmPersonIds", SqlDbType.Text, admPersonIdsForXML.GetXml(),
                        "@filterByLatestReportingPeriod", SqlDbType.Bit, filterByLatestReportingPeriod)))
                    {

                        while (rdrRptDetails.Read())
                        {
                            pdfToolKit.InputByteArray = (byte[])rdrRptDetails["BLOB"];
                            pageCount += pdfToolKit.NumPages("MEMORY");


                            try
                            {
                                pdfToolKit.CopyForm(0, 0);
                                pdfToolKit.AddInternalLinkBookmark(rdrRptDetails["FullName"].ToString(), nextBookMark, 0, 0);
                                nextBookMark = pageCount + 1;
                            }
                            finally
                            {
                                pdfToolKit.CloseInputFile();
                            }
                        }
                    }

                }
                finally
                {
                    pdfToolKit.CloseOutputFile();
                    System.GC.Collect();
                }
                CDS.Document doc = new CDS.Document(new Policy.NullCachePolicy());
                doc.Name = "DetailedReport.pdf";
                doc.Blob = pdfToolKit.BinaryImage();

                //Move the content of the temporary file to the file in Staged view app folder available on the webserver
                string outputFile = doc.WriteTemporaryFile(".pdf");
                return WriteFileToStagingFolder(stagedOutputFolder, outputFile);
            }
            catch (Exception ex)
            {
                throw new Exception("Failed to generate the detailed report.", ex);
            }

        }

        /// <summary>
        /// Returns the summary report for the specified COI Ids
        /// </summary>
        /// <returns>A Document object</returns>
        public CDS.Document GetSummaryReport(string appPath, DataSet admPersonIdsForXML, string supervisorName, bool filterByLatestReportingPeriod)
        {
            MemoryStream xmlStream = null;
            FileStream xslStream = null;
            MemoryStream pdfStream = null;
            try
            {
                string connectionString = Utility.DataAccess.ConnectionString;
                FODocument foDocument = new FODocument();

                string xslFilePath = Path.Combine(appPath, Utility.Settings.GetKeyValue("COISummaryXSLFOFileName", "XSLFO\\COISummaryReport.xsl"));
                string IbexLicenseFileName = "IbexLicenseFile";
                ibex4.licensing.Generator.LicenseFileLocation = Path.Combine(appPath, Utility.Settings.GetKeyValue(IbexLicenseFileName, "License\\xmlpdf.Lic"));

                string logoPath = Path.Combine(appPath, "..");
                logoPath = Path.Combine(logoPath, Utility.Settings.GetKeyValue("PartnersLogo", ""));

                DataTable coiDetails = Utility.DataAccess.GetDataTable(connectionString, "GetCOISummaryXML",
                    Utility.DataAccess.BuildSqlParameterArray("@supervisorName", SqlDbType.VarChar, supervisorName,
                    "@xmlListOfAdmPersonIds", SqlDbType.Text, admPersonIdsForXML.GetXml(),
                    "@filterByLatestReportingPeriod", SqlDbType.Bit, filterByLatestReportingPeriod));

                DataRowCollection rows = coiDetails.Rows;
                string coiXML = string.Empty;
                if (rows.Count > 0)
                    coiXML = rows[0][0].ToString();

                xmlStream = new MemoryStream(Encoding.UTF8.GetBytes(coiXML));
                xslStream = new FileStream(xslFilePath, FileMode.Open, FileAccess.Read);
                pdfStream = new MemoryStream();
                try
                {
                    using (xslStream)
                    {
                        foDocument.generate(xmlStream, xslStream, pdfStream, false);
                    }
                }
                catch (Exception)
                {
                    string bvh = string.Empty;
                }

                CDS.Document doc = new CDS.Document(new Policy.NullCachePolicy());
                doc.Name = "SummaryReport.pdf";

                doc.Blob = pdfStream.ToArray();
                return doc;
            }
            catch (Exception e)
            {
                throw new Exception("Failed to generate the summary report.", e);
            }
            finally
            {
                if (xmlStream != null)
                    xmlStream.Close();
                if (xslStream != null)
                    xslStream.Close();
                if (pdfStream != null)
                    pdfStream.Close();
            }
        }

        public string CreateFolderHierarchy(int protocolId, int docId, string fileName)
        {
            Policy.ICachePolicy cachePolicy = new Policy.NullCachePolicy();
            Protocol protocol = new Protocol(cachePolicy);
            protocol.Load(Utility.DataAccess.ConnectionString, protocolId);
            string folderHierarchy = string.Empty;

            string documentId = (docId == 0 ? Constants.IdPrefix : docId.ToString());
            string filExtension = fileName.Substring(fileName.LastIndexOf('.'), fileName.Length - (fileName.LastIndexOf('.')));
            string moduleName = protocol.ModuleType == "H" ? "Humans" : "Animals";
            string url = Utility.Settings.GetKeyValue("SharePointBlobURL", string.Empty);
            string docLibName = Utility.Settings.GetKeyValue("DocLibName", "Document");

            if (string.IsNullOrEmpty(protocol.ProtocolNumber))
            {
                url += "/" + moduleName + "/" + DateTime.Now.Year + "/" + docLibName;
            }
            else
            {
                url += "/" + moduleName + "/" + protocol.ProtocolNumber.ToString().Substring(0, 4) + "/" + docLibName;
            }
            folderHierarchy = url + "/" + protocol.Id + "/" + documentId + filExtension;

            return folderHierarchy;

        }

        private Hashtable GetMetaDataHashTable(string[] metadata)
        {

            Hashtable htMetadata = new Hashtable();
            // Get the upper bound to loop.
            for (int iCount = 0; iCount < metadata.Length; iCount++)
            {
                htMetadata[metadata[iCount]] = metadata[++iCount];

            }
            return htMetadata;
        }


        [WebMethod]
        [SoapDocumentMethod(OneWay = true)]
        public void DeleteViewAppDocuments(int protocolProcessId, int protocolId)
        {
            DeleteAppDocuments(protocolProcessId, protocolId);
        }
        /// <summary>
        /// The method deletes all Application PDF(View Full App, View App, Current View, IR) on sharepoint
        /// identified for this protocolprocessid
        /// </summary>
        /// <param name="protocolProcessId"></param>
        /// <param name="protocolId"></param>
        private void DeleteAppDocuments(int protocolProcessId, int protocolId)
        {
            try
            {
                DocumentLibrary docLib = new DocumentLibrary();
                IRBDocment irbDocument = new IRBDocment(new Policy.NullCachePolicy());
                //Delete View Full App
                string folderHierarchy = string.Empty;

                try
                {
                    folderHierarchy = irbDocument.CreateFolderHierarchy(protocolProcessId, protocolId, Constants.ViewApplicationType.View);
                    docLib.DeleteDocument(folderHierarchy);
                }
                catch{
                    throw;
                }

                try
                {
                    //Delete Full App
                    folderHierarchy = folderHierarchy.Replace(Constants.ViewApplicationType.View, Constants.ViewApplicationType.Full);
                    //folderHierarchy = irbDocument.CreateFolderHierarchy(protocolProcessId, protocolId, Constants.ViewApplicationType.Full);
                    docLib.DeleteDocument(folderHierarchy);
                }
                catch
                {
                    throw;
                }

                try
                {
                    //Delete Current View
                    folderHierarchy = folderHierarchy.Replace(Constants.ViewApplicationType.Full, Constants.ViewApplicationType.Simple);
                    //folderHierarchy = irbDocument.CreateFolderHierarchy(protocolProcessId, protocolId, Constants.ViewApplicationType.Simple);
                    docLib.DeleteDocument(folderHierarchy);
                }
                catch
                {
                    throw;
                }
                try
                {
                    //Delete Current View
                    folderHierarchy = folderHierarchy.Replace(Constants.ViewApplicationType.Simple, Constants.ViewApplicationType.FullUsingProtocolInformation);
                    //folderHierarchy = irbDocument.CreateFolderHierarchy(protocolProcessId, protocolId, Constants.ViewApplicationType.FullUsingProtocolInformation);
                    docLib.DeleteDocument(folderHierarchy);
                }
                catch
                {
                    throw;
                }


            }
            catch (Exception ex)
            {
                string text = string.Format("Failed to delete Frozen PDF:ProtocolProcessId={0};protocolid={1}", protocolProcessId.ToString(), protocolId.ToString());
                Utility.EmailNotification.SendEmail(text + ex.Message + " - \r Inner Exception: " + ex.StackTrace);

            }
        }
    }


}



